001 /** 002 * Created by IntelliJ IDEA. 003 * User: Wei Wang 004 * Date: Nov 30, 2002 005 * Time: 2:13:56 PM 006 */ 007 008 package EVolve.visualization.XYViz.ValValViz; 009 010 import EVolve.util.*; 011 import EVolve.util.painters.RandomPainter; 012 import EVolve.data.*; 013 import EVolve.visualization.*; 014 import EVolve.visualization.Dimension; 015 import EVolve.Scene; 016 import javax.swing.*; 017 import java.util.*; 018 import java.awt.event.*; 019 import java.awt.*; 020 021 public class StackViz extends ValueValueVisualization{ 022 private ArrayList menuList; 023 private JMenuItem itemChangeThread; 024 private HashMap methodStacks; 025 private ThreadChooser td; 026 private JTextField textBegin, textEnd; 027 private Stack stack; 028 private int event; 029 private JMenuItem itemSelectTimeFrame, itemSelectOccurredEntities; 030 private static JMenuItem selectionMenu[] = null; 031 private String selected; 032 protected static int SELECT_OPTION = 0x0011; 033 private JLabel toEventNo; 034 035 036 public StackViz() { 037 super(); 038 039 menuList = new ArrayList(); 040 imageMap = new HashMap(); 041 methodStacks = new HashMap(); 042 td = new ThreadChooser(imageMap,false); 043 044 interval = 1; 045 beginCall = 0; 046 endCall = 300; 047 } 048 049 public Dimension[] createDimension() { 050 Dimension [] returnDimension = new Dimension[3]; 051 052 xAxis = new ValueDimension(); 053 entityIdFilter = new ReferenceDimension(); 054 filter2 = new ReferenceDimension(); 055 056 returnDimension[0] = xAxis; 057 returnDimension[1] = entityIdFilter; 058 returnDimension[2] = filter2; 059 060 return returnDimension; 061 } 062 063 protected void updateConfiguration() { 064 try { 065 beginCall = Integer.parseInt(textBegin.getText()); 066 endCall = Integer.parseInt(textEnd.getText()); 067 068 canvas.setName("Time - Invocations", "Stack"); 069 super.updateConfiguration(); 070 } catch (NumberFormatException e) { 071 Scene.showErrorMessage("Begin call and end call must be an integer and smaller than "+Integer.MAX_VALUE+"."); 072 configure(); 073 }; 074 } 075 076 public HashMap getCurrentConfigure() { 077 HashMap configure = super.getCurrentConfigure(); 078 079 configure.put("Interval", new Integer(interval)); 080 configure.put("BeginCall", new Long(beginCall)); 081 configure.put("EndCall", new Long(endCall)); 082 083 return configure; 084 } 085 086 public void preVisualize() { 087 xMax = 0; 088 event = 0; 089 stack = null; 090 image = null; 091 imageMap.clear(); 092 methodStacks.clear(); 093 currentThread = -1; 094 getSelection(); 095 installPainter(); 096 super.preVisualize(); 097 } 098 099 public void receiveElement(Element element) { 100 long methodId = entityIdFilter.getField(element); 101 long threadId = filter2.getField(element); 102 long callno = xAxis.getField(element) - 1; 103 104 countEvents(callno/2); 105 106 switchThread(threadId); 107 108 if ((callno<beginCall*2) || (callno>endCall*2+1)) { 109 if (element.isOptional()) {// method return; 110 if (!stack.empty()) stack.pop(); 111 } else 112 stack.push(new Long(methodId)); 113 return; 114 } 115 116 event++; 117 if (!element.isOptional()) // method enter; 118 stack.push(new Long(methodId)); 119 120 for (int j=0;j<stack.size();j++) { 121 painter.paint(image,callno-beginCall*2,j,((Long)stack.get(j)).intValue()); 122 } 123 124 if (element.isOptional()) {// method return; 125 if (!stack.empty()) stack.pop(); 126 } 127 } 128 129 public void visualize() { 130 if (imageMap.size() == 0 ) return; 131 while (selected==null) { 132 selected = td.showDialog(); 133 if (selected != null) { 134 image = (AutoImage)imageMap.get(new Long(selected.substring(7,selected.length()))); 135 canvas.setName("Time - "+ xAxis.getDataFilter().getName() + "(" + event/2 +" events)", "Stack"); 136 sort(); 137 selected = null; 138 break; 139 } 140 } 141 } 142 143 public void makeSelection() { 144 if (SELECT_OPTION == 0) { 145 Scene.showErrorMessage("No data is to be selected."); 146 return; 147 } 148 149 if (dataSourceId != Scene.getDataSourceManager().getCurrentDataSourceId()) { 150 Scene.showErrorMessage("The active data source used currently is different from \n" + 151 "this visualization, please choose \"" + 152 Scene.getDataSourceManager().getUsedDataSourceName(dataSourceId)+"\"."); 153 return; 154 } 155 156 int x1 = canvas.getStartX(); 157 int x2 = canvas.getEndX(); 158 int y1 = canvas.getEndY(); 159 int y2 = canvas.getStartY(); 160 161 if (!normalOrientation) { 162 int temp; 163 temp = x1; 164 x1 = y1; 165 y1 = temp; 166 temp = x2; 167 x2 = y2; 168 y2 = temp; 169 } 170 171 if (((x1<0)&&(x2<0)) || ((x1/2>=timeMap.size()))&&(x2/2>=timeMap.size())) 172 return; 173 174 if (x1 < 0) x1 = 0; 175 176 if (x2/2 > timeMap.size()) 177 x2 = (timeMap.size()-1)*2; 178 179 180 long start, end; 181 if ((SELECT_OPTION & 0x000f) == 0) { 182 start = 0; 183 end = Long.MAX_VALUE; 184 } else { 185 long eventInterval[] = (long[])timeMap.get((int)(x1/2+beginCall)); 186 start = eventInterval[1]; 187 eventInterval = (long[])timeMap.get((int)(x2/2+beginCall)); 188 end = eventInterval[1]; 189 } 190 191 if (y1 < 0) y1 = 0; 192 193 int methodId; 194 ArrayList idList = new ArrayList(); 195 for (int i = x1; i <= x2; i++) { 196 for (int j = y1; j <= y2; j++) { 197 if (normalOrientation) 198 methodId = (int)getEntityId(i,j); 199 else 200 methodId = (int)getEntityId(j,i); 201 if ((methodId == -1)||(idList.contains(new Integer(methodId)))) continue; 202 idList.add(new Integer(methodId)); 203 } 204 } 205 206 207 int selection[] = null; 208 209 if ((SELECT_OPTION & 0x00f0) == 0x0010) { 210 selection = new int[idList.size()]; 211 for (int i=0; i<selection.length; i++) 212 selection[i] = ((Integer)idList.get(i)).intValue(); 213 } else { 214 selection = new int[entityIdFilter.getEntityNumber()]; 215 for (int i=0; i<selection.length; i++) 216 selection[i] = i; 217 } 218 219 entityIdFilter.makeSelection(subjectDefinition.getType(),selection,start,end,timeMap); 220 } 221 222 protected void mouseMove(int x, int y) { 223 int X = canvas.getImageX(x); 224 int Y = canvas.getImageY(y); 225 226 if ((X>=0) && (Y >= 0)) { 227 if (image.getSortedColor(null,null,X,Y)==null) 228 Scene.setStatus(" "); 229 else 230 Scene.setStatus(getEntityName(X,Y)+" "+X+":"+Y); 231 } else { 232 Scene.setStatus(" "); 233 } 234 } 235 236 protected ArrayList createOptionalMenu() { 237 if (menuList.size() > 0) return null; 238 239 menuList.clear(); 240 itemChangeThread = new JMenuItem("Switch thread..."); 241 itemChangeThread.setMnemonic(KeyEvent.VK_T); 242 itemChangeThread.addActionListener(new ActionListener() { 243 public void actionPerformed(ActionEvent e) { 244 visualize(); 245 } 246 }); 247 248 menuList.add(itemChangeThread); 249 return menuList; 250 } 251 252 private String getEntityName(int x, int y) { 253 String returnVal = ""; 254 int mappedId = (int)getEntityId(x,y); 255 Entity entity = entityIdFilter.getEntityFromInt(mappedId); 256 257 if (entity != null) returnVal = entity.getName(); 258 return returnVal; 259 } 260 261 private long getEntityId(int x, int y) { 262 Color color = image.getSortedColor(null,null,x,y); 263 if ((color == null)||(painter == null)) return -1; 264 return ((RandomPainter)painter).getKeyFromColor(color); 265 } 266 267 protected void switchThread(long threadId) { 268 if (currentThread != threadId) { 269 stack = (Stack)methodStacks.get(new Long(threadId)); 270 if (stack == null) { 271 stack = new Stack(); 272 methodStacks.put(new Long(threadId),stack); 273 } 274 super.switchThread(threadId); 275 } 276 } 277 278 protected void installPainter() { 279 painter = new RandomPainter(); 280 } 281 282 public JMenuItem[] createSelectionMenuItem() { 283 if (selectionMenu!=null) return selectionMenu; 284 285 itemSelectTimeFrame = new JCheckBoxMenuItem("Time Frame"); 286 itemSelectTimeFrame.setMnemonic(KeyEvent.VK_T); 287 itemSelectTimeFrame.addActionListener(new ActionListener() { 288 public void actionPerformed(ActionEvent e) { 289 boolean selected = itemSelectTimeFrame.isSelected(); 290 SELECT_OPTION = switchOption(selected, SELECT_OPTION, SELECT_TIME_FRAME); 291 } 292 }); 293 itemSelectTimeFrame.setSelected(true); 294 295 itemSelectOccurredEntities = new JCheckBoxMenuItem("Occurred Entities"); 296 itemSelectOccurredEntities.setMnemonic(KeyEvent.VK_O); 297 itemSelectOccurredEntities.addActionListener(new ActionListener() { 298 public void actionPerformed(ActionEvent e) { 299 boolean selected = itemSelectOccurredEntities.isSelected(); 300 SELECT_OPTION = switchOption(selected, SELECT_OPTION, SELECT_OCCURRED_ENTITIES); 301 } 302 }); 303 itemSelectOccurredEntities.setSelected(true); 304 305 selectionMenu = new JMenuItem[2]; 306 selectionMenu[0] = itemSelectTimeFrame; 307 selectionMenu[1] = itemSelectOccurredEntities; 308 309 return selectionMenu; 310 } 311 312 protected JPanel createConfigurationPanel() { 313 JPanel returnVal = new JPanel(new GridLayout(1, 1, 5, 5)); 314 JPanel panelEvent = new JPanel(new GridLayout(2,2)); 315 316 Box panelBottom = new Box(BoxLayout.Y_AXIS); 317 returnVal.add(panelBottom); 318 319 textBegin = new JTextField(String.valueOf(beginCall)); 320 textEnd = new JTextField(String.valueOf(endCall)); 321 panelEvent.add(new JLabel("From Call No:")); 322 panelEvent.add(textBegin); 323 324 toEventNo = new JLabel("To Call No:"); 325 panelEvent.add(toEventNo); 326 panelEvent.add(textEnd); 327 panelBottom.add(panelEvent); 328 329 return returnVal; 330 } 331 332 protected void updateComboSubject() { 333 super.updateComboSubject(); 334 String range = String.valueOf(Scene.getDataManager().getDataSource().getNumberOfEvents(elementDefinition[comboSubject.getSelectedIndex()].getName())); 335 toEventNo.setText("To Call No:("+range+")"); 336 } 337 338 public Object clone() { 339 StackViz o = (StackViz)super.clone(); 340 o.dimension[0] = o.xAxis; 341 o.dimension[1] = o.entityIdFilter; 342 o.dimension[2] = o.filter2; 343 344 345 o.td = new ThreadChooser(o.imageMap,false); 346 347 o.methodStacks = new HashMap(); 348 Iterator it = methodStacks.keySet().iterator(); 349 while (it.hasNext()) { 350 Object key = it.next(); 351 Stack newStack = new Stack(), oldStack = (Stack)methodStacks.get(key); 352 o.methodStacks.put(key,newStack); 353 for (int i=0; i<oldStack.size(); i++) 354 newStack.add(oldStack.get(i)); 355 } 356 357 o.menuList = new ArrayList(); 358 o.createDialog(); 359 return o; 360 } 361 362 }